/*
 * @Author: your name
 * @Date: 2020-12-11 13:37:39
 * @LastEditTime: 2020-12-28 14:17:47
 * @LastEditors: Please set LastEditors
 * @Description: 子页面的相关操作
 * @FilePath: \gitee-WeBi\js\zz\tabs\tabs.js
 */
(function(){
    /**
     * @description: 创建tab对象
     * @param {*  options
     *  xh: 对象标识
     *  tabPagesId: tab栏对象id
     *  tabContentId: tab页面容器的id
     *  
     * @return {*}
     */
    function Tab(options){
        var options = options || {};
        // 参数
        this.options = $.extend(
            true,
            {
                emptyClass:".zz-not-exist", // 用来创建一个空的jq对象
                xh:0, // --- 页面上可能有多个tab对象
                tabPagesId:"zz-pagetabs", // 切换子页面的tab栏jq对象的id，默认
                pageContentClass:".zz-body", // --- 页面内容区的类名
                pCCSideMenuHide:"sideMenuHide", // --- 侧边栏隐藏时tab栏对应的类名
                pCCSideMenuToggle:"sideMenuToggle", // --- 侧边栏折叠时tab栏对应的类名
                pageCCTabHide:"tabHide", // --- tab栏收起时页面内容区对应的类名(top变化)
                tabContentId:"zz-body-content",  // 存放子页面的jq对象的id，默认
                sideMenuName:"zzSideMenu",  // 页面切换时需要和左侧菜单对应???
                cacheDataName:"zzTabsCache",  // 存tab数据的属性名 --- 缓存
                cacheDataCurName:"zzTabsCacheCur", // 存tab数据的属性名(当前显示的子页面) --- 缓存
                initUrl:"",  // 打开页面时默认打开的子页面
                initTabTitle:"标题", // 默认子页面的标题
                showAfterInit:true, // 初始化完成后是否立即加载显示子页面
                firstTabItemIconSrc:"../../../images/zzHeader/logo.png", // 默认打开的tabitem的icon图片链接
                tabTitlesW:0, // tab项容器的宽度(左右移动时用)
                tabUpTop:64, // --- tab栏收起时的内容区top值（根据css样式）
                tabDownTop:104 // --- tab栏展开时的内容区top值（根据css样式）
            },
            options
        );
        // 
        this.tabPages = $("#"+this.options.tabPagesId+this.options.xh).html(this.contentHtml); // --- tab栏最外层对象
        this.tabPagesHeight = 0; // --- tab栏的高度(收起tab栏的时候用)
        this.tabItems = $(this.options.emptyClass);  // tabitem的集合--jq对象--tab
        this.tabBodyWrap = $("#"+this.options.tabContentId+this.options.xh); // tabbody的集合的容器
        this.tabBodys = $(this.options.emptyClass); // --- tabbody的集合--jq对象--子页面
        // --- 已经创建的tab
        this.openedTabMenu = {};   
        // --- 当前显示tab
        this.curTabMenu = {}; 
        // --- tabList左右滑动的数据
        this.slideIndex = 0;
        this.tabSlideInfo = [];
        // --- 侧边栏的引用
        this.sideMenu = null;
        // --- 初始化
        this.init();
    }
    /*  */
    Tab.prototype = {
        constructor:Tab,
        // tab布局结构
        contentHtml:`
            <div class="zz-pagetabs-control zz-pagetabs-icon_prev el-icon-d-arrow-left"></div>
            <div class="zz-pagetabs-control zz-pagetabs-icon_next el-icon-d-arrow-right"></div>
            <div class="zz-pagetabs-control zz-pagetabs-icon_down el-icon-arrow-down">
                <dl class="zz-nav-child">
                    <dd data-event="closeThisTabs"><span href="javascript:;">关闭当前标签页</span></dd>
                    <dd data-event="closeOtherTabs"><span href="javascript:;">关闭其它标签页</span></dd>
                    <dd data-event="closeAllTabs"><span href="javascript:;">关闭全部标签页</span></dd>
                </dl>
            </div>
            <div class="zz-pagetabs_tabs">
                <ul class="zz-pagetabs_tabs_titles"></ul>
            </div>
        `,
        // tabitem的html tab-this
        tabItemHtml:`
            <li class="">
                <span class="tab-text"></span>
                <i class="tab-close el-icon-close"></i>
            </li>
        `,
        // tabcontent的html tab-this
        tabConHtml:`
            <div class="zz-tabsbody-item">
                <iframe class="zz-tabsbody-item_iframe" src="" frameborder="0"></iframe>
            </div>
        `,
        /**
         * @description: tab初始化
         * @param {*}
         * @return {*}
         */
        init(){
            // --- tab栏放tab
            this.tabPagesList = this.tabPages.find(".zz-pagetabs_tabs_titles"); 
            // --- 更新tabitems
            this.refreshTabItems();
            // --- 更新tabbodys
            this.refreshTabBodys();
            this.tabPrev = this.tabPages.find(".zz-pagetabs-icon_prev"); // --- tab栏左滑箭头
            this.tabNext = this.tabPages.find(".zz-pagetabs-icon_next"); // --- tab栏右滑箭头
            this.tabDropDown = this.tabPages.find(".zz-pagetabs-icon_down"); // --- tab栏下拉箭头
            this.navChildMenu = this.tabPages.find(".zz-nav-child"); // --- 下拉菜单
            // --- tabItems容器的宽度
            this.options.tabTitlesW = this.tabPagesList.innerWidth();
            // --- tab栏的高度
            this.tabPagesHeight = this.tabPages.innerHeight();
            // --- 根据缓存的数据创建tab
            this.createTabsByCache();
            // --- tabitems绑定事件
            this.tabItemsBindEvent();
            // --- 计算tabList的滑动距离
            this.calcTabListSlideInfo();
            // --- tabList滑动到当前显示的tabitem
            this.tabListSlideByCur();
            // --- 获取侧边栏引用
            this.getSideMenu();
        },
        /**
         * @description: 循环获取侧边栏引用
         * @param {*}
         * @return {*}
         */
        getSideMenu(){
            if(this.sideMenu)return;
            this.sideMenu = window[this.options.sideMenuName + this.options.xh];
            _.delay(_.bind(function(){
                !this.sideMenu && this.getSideMenu();
            },this),100);
        },
        /**
         * @description: 清空已创建的tabitems的选中样式
         * @param {*}
         * @return {*}
         */
        clearTabItemsShow(){
            this.tabItems.removeClass("tab-this");
        },
        /**
         * @description: 显示当前的tabitem
         * @param {
         * *  dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {*}
         */
        showCurTabItem(dataUrl){
            this.tabItems.filter('[data-url="'+dataUrl+'"]').removeClass("tab-this").addClass("tab-this");
        },
        /**
         * @description: 删除tabitem
         * @param {
         * *  dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {*}
         */
        removeTabItem(dataUrl){
            this.tabItems.filter('[data-url="'+dataUrl+'"]').remove();
            // --- 更新tabitems
            this.refreshTabItems();
        },
        /**
         * @description: 更新tabitems
         * @param {
         * * dataUrl  
         * }
         * @return {*}
         */
        refreshTabItems(){
            this.tabItems = null;
            this.tabItems = this.tabPagesList.children();
        },
        /**
         * @description: 隐藏已创建的tabbodys
         * @param {*}
         * @return {*}
         */
        hideTabBodys(){
            this.tabBodys.removeClass("tab-this");
        },
        /**
         * @description: 显示当前的tabbody
         * @param {
         * *  dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {
         * * 切换后显示的tabbody
         * }
         */
        showCurTabBody(dataUrl){
            try {
                var showTabBody = this.tabBodys.filter('[data-url="'+dataUrl+'"]');
                var childIframe = showTabBody.children("iframe[src]");
                showTabBody.removeClass("tab-this").addClass("tab-this");
                if(childIframe.attr("src")){
                }else{
                    // --- 根据缓存数据创建的tab,重新赋值src
                    childIframe.attr("src",dataUrl);
                }
                // --- openedTabMenu有数据的时候
                if(!$.isEmptyObject(this.openedTabMenu)){
                    // ---
                    document.title = this.openedTabMenu[dataUrl].title;
                    // ---
                    this.curTabMenu = this.openedTabMenu[dataUrl];
                    // --- 缓存当前显示页面的tab数据
                    zzSSSetItem(
                        this.options.cacheDataCurName + this.options.xh,
                        this.curTabMenu
                    );
                    // --- 缓存页面的tab数据
                    this.saveOpenedTab(this.curTabMenu);
                }
                //
                return showTabBody;
            } catch (error) {
                console.warn("---showCurTabBody出错啦---",error);
                return $(this.options.emptyClass);
            }
        },
        /**
         * @description: 更新tabbodys
         * @param {*}
         * @return {*}
         */
        refreshTabBodys(){
            this.tabBodys = null;
            this.tabBodys = this.tabBodyWrap.children();
        },
        /**
         * @description: 删除tabbody
         * @param {
         * *  dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {*}
         */
        removeTabBody(dataUrl){
            this.tabBodys.filter('[data-url="'+dataUrl+'"]').remove();
            // --- 更新tabitems
            this.refreshTabBodys();
        },
        /**
         * @description: 切换显示与url对应的tabitem和tabbody
         * @param {* 
         *  dataUrl  标签创建时添加的页面地址(iframe)
         *  data   创建tab项的信息
         * }
         * @return {*}
         */
        tabChange(dataUrl,data){
            var data = data || {};
            try {
                // 清空已创建的tabitem的样式
                this.clearTabItemsShow();
                // 隐藏已创建的tabbody
                this.hideTabBodys();
                // --- 显示对应的tabitem 和 tabbody
                // --- (hideTabSideMenu:是否需要隐藏tab栏和sideMenu侧边栏)
                if(data.hideTabSideMenu){
                    this.hideTab().then($.proxy(function(){
                        this.showCurTabItem(dataUrl);
                        this.showCurTabBody(dataUrl);
                    },this));
                }else{
                    this.showCurTabItem(dataUrl);
                    this.showCurTabBody(dataUrl);
                }
                // --- 切换子页面后是否需要刷新子页面 ???
                //this.tabBodyRefresh(dataUrl);
            } catch (error) {
                console.warn("---tabChange出错啦---",error);
            }
        },
        /**
         * @description: 刷新子页面窗口
         * @param {
         * * dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {*}
         */
        tabBodyRefresh(dataUrl){
            try {
                this.tabBodys.filter('[data-url="'+dataUrl+'"]').children("iframe[src]").get(0).contentWindow.location.reload();
            } catch (error) {
                console.warn("---tabRefresh出错啦---",error);
            }
        },
        /**
         * @description: tab添加子页面
         * @param {* info对象 {}
         *     url: 子页面链接 string
         *     title: 子页面简易描述 string 
         *     hideTabSideMenu: 显示子页面时是否收起tab栏和侧边栏
         *     noOpenMenuItem: 点击侧边栏菜单项时调用tabAdd只匹配url,不展开菜单项
         *     posResize: tab栏左右2测的tabitem显示不完全的时候调整显示位置     
         * }
         * @return {*}
         */
        tabAdd(info){
            var _this = this;
            try {
                var info = info || {};
                if($.isEmptyObject(info)||!info.url){
                    console.warn("---tab.tabAdd---:添加子页面需要链接地址");
                    return;
                }
                // --- 
                // --- 页面是否已经创建
                var pageCreated = false;
                this.tabItems.each(function(i,e){
                    if($(e).attr("data-url") == info.url){
                        pageCreated = true;
                        return false;
                    }
                });
                // --- 页面已创建
                if(pageCreated){
                    //alert("pageCreated");
                    //console.log("---pageCreated_info---",info);
                    // --- 
                    this.tabChange(info.url,info);
                    // --- 侧边栏菜单对应切换 ???
                    //alert(info.noOpenMenuItem);
                    !info.noOpenMenuItem && this.matchSideMenu(info.url);
                    //this.matchSideMenu(info.url);
                    // --- 计算tabList的滑动距离
                    this.calcTabListSlideInfo();
                    // --- tabList滑动到当前显示的tabitem
                    // --- 是否需要调整tabitem的位置
                    info.posResize?this.tabListSlide(info.url):this.tabListSlideByCur();
                    return;
                }
                // --- 是否根据缓存的数据创建tab
                var isCache = info.loadByTabChange?true:false;
                // --- 标记时间戳 ( 重新创建 or 根据缓存数据创建)
                var sjc = +new Date();
                //
                var title = info.title || "请写一点页面描述吧...";
                // --- 创建tabitem
                var tabLength = this.tabItems.length;
                var closeIconHtml = tabLength>0?'<i class="tab-close el-icon-close"></i>':''; // --- 默认页不要删除图标
                var initPageIcon =  tabLength>0?'':'<img class="first-tabitem-icon" src="'+this.options.firstTabItemIconSrc+'" alt="666" />'; // --- 默认页的tabitem加个icon
                var delayLoadFlag = isCache?"yes":"";  // --- 如果是从缓存的数据中创建tab，加标记
                this.tabPagesList.append(
                    '<li class="" title="'+title+'" data-url="'+info.url+'" data-id="'+sjc+'" data-delay="'+delayLoadFlag+'">'+
                        initPageIcon+
                        '<span class="tab-text">'+title+'</span>'+
                        closeIconHtml+
                    '</li>'
                );
                // --- 创建tabbody
                var iframeSrc = isCache?"":info.url;  // --- 如果是从缓存的数据中创建tab，先不跟iframe加src
                this.tabBodyWrap.append(
                    '<div class="zz-tabsbody-item" data-url="'+info.url+'" data-id="'+sjc+'">'+
                        '<iframe class="zz-tabsbody-item_iframe" src="'+iframeSrc+'" frameborder="0" data-id="'+sjc+'"></iframe>'+
                    '</div>'
                );
                // --- 更新tabitems
                this.refreshTabItems();
                // --- 更新tabbodys
                this.refreshTabBodys();
                // --- 是否根据缓存的数据创建tab
                if(isCache){
                    // --- 所有tab项创建完之后
                    if(this.tabItems.length === this.getOpenedTabMenuLen()){
                        // --- 不立即显示页面
                        if(!this.options.showAfterInit)return;
                        var openedTabMenuCur = zzSSGetItem(this.options.cacheDataCurName + this.options.xh);
                        if(openedTabMenuCur){
                            // --- 显示与url对应的页面
                            this.tabChange(openedTabMenuCur.url,openedTabMenuCur);
                            // --- 
                            this.matchSideMenu(openedTabMenuCur.url);
                        }else{
                            // --- 显示与最后一个tabitem对应的页面
                            this.tabBodys.last().children("iframe[src]").attr("src",info.url);
                            // --- 显示与url对应的页面
                            this.tabChange(info.url,info);
                            // --- 
                            this.matchSideMenu(info.url);
                        }
                        // --- 计算tabList的滑动距离
                        this.calcTabListSlideInfo();
                        // --- tabList滑动到当前显示的tabitem
                        this.tabListSlideByCur();
                    }
                }else{
                    // --- 缓存tab数据(不是根据缓存的数据创建时)
                    this.saveOpenedTab($.extend(
                        true,
                        {
                            id:sjc
                        },
                        info
                    ));
                    // --- 显示与url对应的页面
                    this.tabChange(info.url,info);
                    // --- 
                    //this.matchSideMenu(info.url);
                    // --- 计算tabList的滑动距离
                    this.calcTabListSlideInfo();
                    // --- tabList滑动到当前显示的tabitem
                    this.tabListSlideByCur();
                }
            } catch (error) {
                console.warn("---tabAdd出错啦---",error);  
            }
        },
        /**
         * @description: tab删除
         * @param {
         * *  dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {*}
         */ 
        tabRemove(dataUrl){
            // --- 删除tabitem
            this.removeTabItem(dataUrl); 
            // --- 删除tabbody
            this.removeTabBody(dataUrl);
            // --- 删除对应缓存的数据
            delete this.openedTabMenu[dataUrl];
            zzSSSetItem(
                this.options.cacheDataName+this.options.xh,
                this.openedTabMenu
            );
        },
        /**
         * @description: tab(当前显示的)删除后显示前一个tab
         * @param {*}
         * @return {*}
         */
        curTabRemove(dataUrl,$tabItem){
            var $prevItem = $tabItem.prev();
            // --- 要删除的是当前显示的项时，展示前一个tab项
            if($prevItem.length > 0 && $tabItem.hasClass("tab-this")){
                var prevDataUrl = $prevItem.attr("data-url");
                // --- 显示对应的tab项
                this.tabChange(prevDataUrl,this.openedTabMenu[prevDataUrl]||{});
                // --- 侧边栏菜单对应切换 ???
                this.matchSideMenu(prevDataUrl);
                // --- 当前正显示的tab项（缓存）
                zzSSSetItem(
                    this.options.cacheDataCurName+this.options.xh,
                    this.openedTabMenu[prevDataUrl]
                );
                // --- 删除tabitem
                this.tabRemove(dataUrl);
            }else{
                // --- 删除tabitem
                this.tabRemove(dataUrl);
            }
        },
        /**
         * @description: tabitems绑定事件
         * @param {*}
         * @return {*}
         */
        tabItemsBindEvent(){
            var _this = this;
            try {
                // ---
                this.tabPagesList.on("click","li",function(ev){ // --- 点击tabitem切换显示的子页面
                    ev.stopPropagation();
                    var $this = $(this);
                    if($this.hasClass("tab-this"))return;
                    // --- 用url进行匹配
                    var dataUrl = $this.attr("data-url");
                    // --- 切换显示子页面
                    _this.tabAdd($.extend(
                        _this.openedTabMenu[dataUrl],
                        {
                            posResize:true,  // --- 是否需要调整tabitem的位置 true false
                            noOpenMenuItem:false, // --- 是否需要匹配侧边栏菜单项
                        }
                    )); // 
                })  
                .on("click","li > .tab-close",function(ev){ // --- 点击tabitem删除子页面
                    ev.stopPropagation();
                    var $this = $(this);
                    // --- 删除之后展示前一个tab项(如果删除的是当前显示项)
                    var $parent = $this.parent();
                    // --- 用url进行匹配
                    var dataUrl = $parent.attr("data-url");
                    // --- 删除
                    _this.curTabRemove(dataUrl,$parent);
                    // --- 计算tabList的滑动距离
                    _this.calcTabListSlideInfo();
                    // --- tabList滑动到当前显示的tabitem
                    _this.tabListSlideByCur();
                });
                // --- 下拉菜单显示隐藏
                this.tabDropDown.on("mouseenter",$.proxy(function(){
                    if(!this.navChildMenu.attr("style")){
                        this.navChildMenu.css({
                            "top":this.tabDropDown.innerHeight()+"px",
                            "left":"-"+( this.navChildMenu.innerWidth() - this.tabDropDown.innerWidth()*0.8 )+"px"
                        })
                    }
                    this.navChildMenu.show();
                },this)).on("mouseleave",$.proxy(function(){
                    this.navChildMenu.hide();
                },this));
                // --- 下拉菜单各操作项
                this.navChildMenu
                .on("click","[data-event='closeThisTabs']",$.proxy(function(){
                    // --- 关闭当前标签页
                    //console.log("---this.curTabMenu---",this.curTabMenu);
                    var dataUrl = this.curTabMenu.url;
                    if(dataUrl){
                        //console.log("------",this.tabItems.filter('[data-url="'+dataUrl+'"]'));
                        var removeTabItem = this.tabItems.filter('[data-url="'+dataUrl+'"]');
                        // --- 默认打开的tab项不删除
                        if(removeTabItem.find("img[class]").length){
                            return false;
                        }
                        // --- 删除
                        this.curTabRemove(dataUrl,removeTabItem);
                        // --- 计算tabList的滑动距离
                        this.calcTabListSlideInfo();
                        // --- tabList滑动到当前显示的tabitem
                        this.tabListSlideByCur();
                    }
                },this))
                .on("click","[data-event='closeOtherTabs']",$.proxy(function(){
                    // --- 关闭其它标签页(除默认页和当前页)
                    //alert("closeOtherTabs");
                    this.tabItems.each($.proxy(function(i,e){
                        var $e = $(e);
                        var dataUrl = $e.attr("data-url");
                        if(
                            ( $e.find("img[class]").length ) ||
                            ( dataUrl == this.curTabMenu.url )
                        ){
                            return true;
                        }else{
                            // --- 删除tabitem
                            this.tabRemove(dataUrl);
                        }
                    },this));
                    // --- 计算tabList的滑动距离
                    this.calcTabListSlideInfo();
                    // --- tabList滑动到当前显示的tabitem
                    this.tabListSlideByCur();
                },this))
                .on("click","[data-event='closeAllTabs']",$.proxy(function(){
                    // --- 关闭全部标签页(除默认页)
                    //alert("closeAllTabs");
                    this.tabItems.each($.proxy(function(i,e){
                        var $e = $(e);
                        var dataUrl = $e.attr("data-url");
                        if($e.find("img[class]").length){
                            // --- 显示对应的tab项
                            this.tabChange(dataUrl,this.openedTabMenu[dataUrl]||{});
                            // --- 侧边栏菜单对应切换 ???
                            this.matchSideMenu(dataUrl);
                            // --- 当前正显示的tab项（缓存）
                            zzSSSetItem(
                                this.options.cacheDataCurName+this.options.xh,
                                this.openedTabMenu[dataUrl]
                            );
                        }else{
                            // --- 删除tabitem
                            this.tabRemove(dataUrl);
                        }
                    },this));
                    // --- 计算tabList的滑动距离
                    this.calcTabListSlideInfo();
                    // --- tabList滑动到当前显示的tabitem
                    this.tabListSlideByCur();
                },this));
                // --- tab栏左滑动
                this.tabPrev.on("click",$.proxy(function(ev){
                    //alert("tabs_move_left");
                    this.slideIndex--;
                    if(
                        (this.slideIndex <= 0)
                    ){
                        this.slideIndex = 0;
                        // --- tab栏滑动
                        this.tabListSlide();
                        return false;
                    }
                    // --- tab栏滑动
                    this.tabListSlide();
                },this));
                // --- tab栏右滑动
                this.tabNext.on("click",$.proxy(function(ev){
                    //alert("tabs_move_right");
                    if(
                        (this.slideIndex >= this.tabSlideInfo.length)
                    ){
                        this.slideIndex = this.tabSlideInfo.length;
                        return false;
                    }
                    this.slideIndex++;
                    // --- tab栏滑动
                    this.tabListSlide();
                },this));
            } catch (error) {
                console.warn("---tabItemsBindEvent出错啦---",error);
            }
        },
        /**
         * @description: tab切换时，对应的侧边栏也切换
         * @param {
         * * dataUrl  标签创建时添加的页面地址(iframe)
         * }
         * @return {
         * * sideMenu 侧边栏对象 or 空对象
         * }
         */ 
        matchSideMenu(dataUrl){
            var sideMenu = this.sideMenu || window[this.options.sideMenuName + this.options.xh];
            if(sideMenu){
                // --- 侧边栏根据url展开对应项
                sideMenu.openNavMenu(dataUrl);
                // --- 改变top.window地址栏
                sideMenu.refreshLocationHref(dataUrl);
            }
            return sideMenu?sideMenu:{};
        },
        /**
         * @description: 存已创建的menu并加到sessionStorage中
         * @param {
         * * info对象 {}
         *     url: 子页面链接 string
         *     title: 子页面简易描述 string
         *     id:  创建时添加的时间戳 
         * }
         * @return {
         * *
         * }
         */ 
        saveOpenedTab(info){
            var info = info || {};
            if($.isEmptyObject(info))return;
            try {
                this.openedTabMenu[info.url] = $.extend(
                    true,
                    {
                        loadByTabChange:"yes" // --- 根据缓存的数据创建tab,在点击切换时再加载子页面
                    },
                    info
                );
                // --- 数据存缓存
                zzSSSetItem(
                    this.options.cacheDataName+this.options.xh,
                    this.openedTabMenu
                );
            } catch (error) {
                console.warn("---saveOpenedTab出错啦---",error);
            }
        },
        /**
         * @description: 获取openedTabMenu对象属性值的数量
         * @param {*}
         * @return {
         * *  length：openedTabMenu对象属性值的数量
         * }
         */ 
        getOpenedTabMenuLen(){
            var count = 0;
            $.each(this.openedTabMenu, $.proxy(function(k){
                if(this.openedTabMenu.hasOwnProperty(k)){
                    count++;
                }else{
                    return false;
                }
            },this));
            return count;
        },
        /**
         * @description: 获取tabitems的宽度总和
         * @param {*}
         * @return {
         * * sum: 宽度和
         * }
         */
        getAllTabItenWidth(){
            var sum = 0;
            this.tabItems.each(function(i,e){
                sum += $(e).innerWidth();
            });
            return sum;
        },
        /**
         * @description: 根据tabitems计算tab栏是否需要滑动
         * @param {*}
         * @return {
         * * Array [
         *      {
         *         slideDis 滑动距离 
         *      }
         * ]
         * }
         */
        calcTabListSlideInfo(){
            this.slideIndex = 0;
            this.tabSlideInfo = null;
            this.tabSlideInfo = [];
            // --- tabitem的总宽度
            //var tsum = this.getAllTabItenWidth();
            //console.log("---tsum---",tsum);
            //console.log("---this.options.tabTitlesW---",this.options.tabTitlesW);
            this.tabItems.each($.proxy(function(i,e){
                var $e = $(e);
                // --- tabitem的position信息
                var pos = $e.position();
                //console.log("---pos---",pos);
                // --- tabitem的宽度
                var tiw = $e.innerWidth();
                //console.log("---tiw---",tiw);
                //console.log("---this.options.tabTitlesW*xh---",this.options.tabTitlesW*xh);
                // --- tablist实际移动的距离
                var slideInfo = this.tabSlideInfo.length?this.tabSlideInfo[this.tabSlideInfo.length - 1]:{};
                var slideDis = slideInfo.slideDis?slideInfo.slideDis:0;
                // --- 
                if((pos.left + tiw) >= (this.options.tabTitlesW + slideDis)){
                    this.tabSlideInfo.push({
                        //slideDis:pos.left + tiw
                        slideDis:pos.left
                    });
                }
            },this));
            // --- 左右点击滑动的键加些提示
            if(this.tabSlideInfo.length){
                this.tabPrev.attr("title","点击后tab栏向右滑动");
                this.tabNext.attr("title","点击后tab栏向左滑动");
            }
            //console.log("---this.tabSlideInfo---",this.tabSlideInfo);
        },
        /**
         * @description: tabList左右滑动
         * @param {
         * *  dataUrl  子页面链接
         * }
         * @return {*}
         */
        tabListSlide(dataUrl){
            try {
                if(dataUrl){
                    var tabItem = this.tabItems.filter('[data-url="'+dataUrl+'"]');
                    if(!tabItem.length){
                        return console.warn("没找到匹配的tabItem(请检查子页面链接src)");
                    }
                    var pos = $.extend(
                        {
                            width:tabItem.innerWidth()
                        },
                        tabItem.position()
                    )
                    //console.log("---pos---",pos);
                    //console.log("---this.slideIndex---",this.slideIndex);
                    //console.log("---this.tabSlideInfo---",this.tabSlideInfo);
                    var slideIndex = this.slideIndex - 1;
                    var leftDis = zzGetCssPropNum(this.tabPagesList.css("left"));
                    // --- tablist的滑动距离为0时候(初始位置)
                    if(slideIndex < 0){
                        slideIndex = 0;
                        // --- tabitem右边未完全显示（修正tabitem位置）
                        if( this.options.tabTitlesW < (pos.left + pos.width)){
                            var dis = (pos.left + pos.width) - this.options.tabTitlesW;
                            this.tabPagesList.css({
                                "left":-1*dis+"px"
                            });
                        }
                        // --- tabitem左边未完全显示（修正tabitem位置）
                        if(leftDis > pos.left){
                            this.tabPagesList.css({
                                "left":"0px"
                            });
                        }
                    }else{
                        slideIndex = this.slideIndex - 1;
                        var slideDis = this.tabSlideInfo[slideIndex].slideDis;
                        // --- tabitem右边未完全显示（修正tabitem位置）
                        if( (slideDis + this.options.tabTitlesW) < (pos.left + pos.width)){
                            var dis = (pos.left + pos.width) - (slideDis + this.options.tabTitlesW);
                            this.tabPagesList.css({
                                "left":-1*(slideDis+dis)+"px"
                            });
                        }
                        // --- tabitem左边未完全显示（修正tabitem位置）
                        if(leftDis > pos.left){
                            this.tabPagesList.css({
                                "left":-1*slideDis+"px"
                            });
                        }
                    }
                }else{
                    var slideInfo = this.tabSlideInfo[this.slideIndex - 1];
                    if(this.tabSlideInfo.length && slideInfo){
                        this.tabPagesList.css({
                            "left":-1*(slideInfo.slideDis)+"px"
                        });
                    }else{
                        this.tabPagesList.css({
                            "left":"0px"
                        });
                    }
                }
            } catch (error) {
                console.warn("---tabListSlide出错啦---",error);
            }
        },
        /**
         * @description: 根据当前显示的tabitem滑动tabList
         * @param {
         * * 需要调整位置的tabitem对应的url
         * }
         * @return {*}
         */
        tabListSlideByCur(){
            //console.log("---this.curTabMenu---",this.curTabMenu);
            if(this.curTabMenu && !$.isEmptyObject(this.curTabMenu)){
                var curTabItem = this.tabItems.filter('[data-url="'+this.curTabMenu.url+'"]');
                var curTabPos = curTabItem.position();
                var curTabWid = curTabItem.innerWidth();
                //console.log("---curTabItem---",curTabItem);
                //console.log("---curTabItem.position---",curTabItem.position());
                if(this.tabSlideInfo.length){
                    $.each(this.tabSlideInfo,$.proxy(function(i,item){
                        if((curTabPos.left + curTabWid) >= item.slideDis){
                            this.slideIndex = i + 1;
                        }
                    },this));
                }
                // --- tabList滑动到对应的位置
                this.tabListSlide();
            }
        },
        /**
         * @description: 根据缓存的数据创建tab
         * @param {*}
         * @return {*}
         */  
        createTabsByCache(){
            this.openedTabMenu = null;
            this.curTabMenu = null;
            try {
                var cacheData = zzSSGetItem(this.options.cacheDataName+this.options.xh);
                var cacheCurData = zzSSGetItem(this.options.cacheDataCurName + this.options.xh);
                // --- 
                if(cacheData && cacheCurData){
                    this.openedTabMenu = cacheData;
                    this.curTabMenu = cacheCurData;
                    $.each(cacheData,$.proxy(function(k,info){
                        // --- 创建tab
                        this.tabAdd(info);
                        // 
                    },this));
                }else{
                    this.openedTabMenu = {};
                    this.curTabMenu = {};
                    if(!this.options.showAfterInit)return;
                    // --- 打开默认页面
                    if(this.options.initUrl){
                        // --- 
                        this.tabAdd({
                            url:this.options.initUrl,
                            title:this.options.initTabTitle
                        });
                        // --- 
                        this.matchSideMenu(this.options.initUrl);
                    }
                }
            } catch (error) {
                console.warn("---createTabsByCache出错啦---",error);
            }
        },
        /**
         * @description: 隐藏tab栏
         * @param {
         *  * callback: 回调（页面布局有相应的调整）
         * }
         * @return {*}
         */
        hideTab(callback){
            var _this = this;
            try {
                // --- 内容区元素
                var zzBodyArea = this.tabBodyWrap.closest(this.options.pageContentClass);
                if(!zzBodyArea.length)return $.Deferred();
                return $.Deferred(function(defer){
                    // --- 内容区布局调整
                    zzBodyArea.addClass(_this.options.pageCCTabHide);
                    $.when(
                        // --- 收起tab栏
                        _this.tabPages.slideUp().promise(),
                        // --- 隐藏侧边栏
                        _this.sideMenu.hideSideMenu()
                    ).then(defer.resolve);
                }).then(function(){
                    // ---
                    _this.tabPages.addClass(_this.options.pCCSideMenuHide);
                    callback && callback();
                });
            } catch (error) {
                console.warn("---隐藏tab栏出错啦---",error);
                return $.Deferred();   
            }
        },
        /**
         * @description: 显示tab栏
         * @param {*}
         * @return {*}
         */
        showTab(callback){
            var _this = this;
            try {
                // --- 内容区元素
                var zzBodyArea = this.tabBodyWrap.closest(this.options.pageContentClass);
                if(!zzBodyArea.length)return $.Deferred();
                return $.Deferred(function(defer){
                    // --- 内容区布局调整
                    zzBodyArea.removeClass(_this.options.pageCCTabHide);
                    $.when(
                        // --- 收起tab栏
                        _this.tabPages.slideDown().promise(),
                        // --- 显示侧边栏
                        _this.sideMenu.showSideMenu()
                    ).then(defer.resolve);
                }).then(function(){
                    // ---
                    _this.tabPages.removeClass(_this.options.pCCSideMenuHide);
                    callback && callback();
                });
            } catch (error) {
                console.warn("---显示tab栏出错啦---",error);
                return $.Deferred();
            }
        }        
    };
    /*  */
    window.zzTab = Tab;
})();